import boid from '../../base/boid'
import { BoidStatus, BoidSkill, BoidBuff } from '../../../config/boid_def';
import { CollisionTag, Tower2Way, CardType, TowerList, WayInfo, GetBuffType } from '../../../config/play_def';

cc.Class({
    extends:boid
    ,

    properties: {
        model: sp.Skeleton,
        model_widget: cc.Widget,
        hp_label: cc.Label,
        lastAni: '',
        name_label:cc.Label,
    },
    initInfo(param, order, insert) {
        this._super(param, order)
        //console.log(param,parseInt(param))
        this.info = he.db.getData("Monster", parseInt(param))

        this.collision.tag = CollisionTag.MONSTER  // 碰撞设置
        this.collision.enabled = false
        this.type = this.info.type
        // 换皮肤部分
        let spData = he.load.get(this.info.model, sp.SkeletonData, 'monster')
        this.model.skeletonData = spData
        this.model.defaultSkin = this.info.skin
        this.model.setSkin(this.info.skin)
        this.model.defaultAnimation = `run`
        this.changeAni(`run`)
        // 生命值赋值
        this.HP = this.info.hp
        this.HP_value = this.HP
        this.Hp_max = this.HP

        // 攻击速度设置
        this._attackSpeed = this.info.attackSpeed
        //console.log("攻击速度"+this._attackSpeed)

        // boss设定
        this.rank=this.info.rank
        this.isHit=true
        if (this.rank ==5) {
            this.node.scale=3
            this.model.timeScale=0.33
            this.isHit=false
            // this.model.timeScale=0.5
            // he.log(this.model.timeScale)
        }
        else
        {
            this.node.scale=1
            this.model.timeScale=1
        }
        // this.hp_label.string = `${this.HP} / ${this.Hp_max}`    // 一般注释掉
        // this.node.getChildByName('id').getComponent(cc.Label).string = this.info.name
        // 伤害速度
        this.damege = this.info.attack  // 伤害
        this.name_label.string = this.info.name
        this.range = this.info.range
        this.melee = this.info.melee
        this._speed = this.info.speed   // 速度
        
        // 位置和碰撞
        this.model_widget.bottom = this.info.fixY
        this.model_widget.updateAlignment()

        if (this.info.collider) {
            let collider_str_list = this.info.collider.split('#')
            let collider_list = []
            for (let i = 0; i < collider_str_list.length; i++) {
                let collider_str = collider_str_list[i].split('_')
                collider_list.push(cc.v2(parseInt(collider_str[0]), parseInt(collider_str[1])))
            }
            this.collision.points = collider_list
        }
        // 护甲类型赋值
        this.armor = this.info.armor
        // 是否飞行单位
        if (this.info.fly)
            this.fly = true
        // 是否插入
        if (!insert) {
            this.ready2ground()
        }
        this.initSkill()
        this.onSpineListen()
    },
    Dead(param) {
        this.deadSkill()
        this.changeAni('die')
    },
    // 动画播完后监听
    onSpineListen() {
        this._setMix('hit', 'run')
        this.model.setCompleteListener((trackEntry) => {
            var animationName = trackEntry.animation ? trackEntry.animation.name : "";
            this.listenComTag(animationName)
        });
        this.model.setEventListener((trackEntry, event) => {
            if(event && event.data && event.data.name){
                let tag =  event.data.name
                this.listenAniTag(tag)
            }
        })
    },
    listenAniTag(tag){
        switch(tag){
            case "attack":    
                if(this.melee){
                    this.attack()
                }else{
                    // if(!this.node.active){
                    //     return
                    // }
                    // if(this.order_line <= 0 || !this.order_line){
                    //     return
                    // }                    
                    let fin_pos = gg.control.wall_pos[this.order_line]
                    let bullet = {
                        pos : this.getWorldPos(),   // 子弹位置
                        damege: this.damege,        // 伤害
                        script:this.info.bullet,            // 子弹脚本
                        voice: this.info.bulletVoice,       // 子弹声音
                        speed: this.info.bulletSpeed,       // 子弹速度
                        attack_fly: true,                   // 是否可攻击空中单位
                        fin_pos:fin_pos,                    // 重点坐标
                        order_line:this.order_line,         // 子弹队列
                        dir: cc.v2(0,-1),                   // 子弹方向
                        style:{                             // 子弹样式
                            skin: this.info.bulletSkin,
                            url:'spine/bullet/' + this.info.bulletModel,
                            type:sp.SkeletonData
                        },
                        effect:[],             
                    }
                    gg.bulletManager.addDeBullet(bullet)
                    // 创建子弹
                    this.status = BoidStatus.Attack 
                }
            break
        }
    },
    // 清理信息
    clearInfo(delNode) {
        this.clearSkill()
        this.model.setCompleteListener(null)
        this.lastAni = ``
        this._super(delNode)
    },
    hpHurt(from, v, noani) {
        this._super(from, v, noani)
        // this.hp_label.string = `${this.HP} / ${this.Hp_max}`    // 一般注释掉
    },
    hurtAni() {
        switch(this.status){
            case BoidStatus.Playing:
                return
        }
        if(this.isHit){
            this.changeAni('hit')
        }
    },
    attackAni(){
        this.changeAni('attack')
    },
    // 动画播完后监听事件
    listenComTag(ani) {
        switch (ani) {
            case 'hit':
                this.changeAni('run')
                break
            case 'die':
                this.clearInfo(true)
            break
            case 'attack':
                this.standAni()
            break
        }
    },
    // 更换动画
    changeAni(ani) {
        if(this.status == BoidStatus.Dead){
            return
        }
        if (this.lastAni == ani || !ani) {
            return
        }
        this.lastAni = ani
        if (this.rank==5&&this.lastAni=="run") {
            this.model.timeScale=0.33
            // he.log("切换run动画")
            // he.log(this.model.timeScale)
        }
        else
        {
            this.model.timeScale=1
        }
        switch (this.lastAni) {
            case 'die':
                this.status = BoidStatus.Dead
                this.model.setAnimation(0, ani, true)
                break
            case 'hit':
                this.model.setAnimation(0, ani, false)
                break
            default:
                this.model.setAnimation(0, ani, true)
                break
        }
    },
    standAni(){
        this.changeAni("stand_by")
    },
    // 从地平线进入视野
    ready2ground() {
        this.status = BoidStatus.Ready
        this.move = true
        this.changeAni('run')
        this.node.y = 0
    },
    _setMix(anim1, anim2) {
        this.model.setMix(anim1, anim2, common.SPINE_MIX_TIME);
        this.model.setMix(anim2, anim1, common.SPINE_MIX_TIME);
    },
    // 阵亡后技能
    deadSkill() {
        if (this.info && this.info.skill) {
            let skill_list = this.info.skill.split("#")
            let skill_param_list
            if (this.info.skillParam)
                skill_param_list = this.info.skillParam.split("#")
            for (let i = 0; i < skill_list.length; i++) {
                let skill_param
                if (skill_param_list)
                    skill_param = skill_param_list[i]
                switch (parseInt(skill_list[i])) {
                    case BoidSkill.D_Throw:
                        let dthrow_param = skill_param.split("/")
                        let throwPos = this.getWorldPos()
                        let throwEffect = {
                            pos: throwPos,
                            pool: 'projectile',
                            prefab: 'effect/projectile',
                            skill: BoidSkill.D_Throw,
                            time: parseInt(dthrow_param[0]),
                        }
                        for (let t = 0; t < parseInt(dthrow_param[1]); t++) {
                            game_main.bulletManager.addTopEffect(throwEffect)
                        }
                        break
                    case BoidSkill.D_GOAL:
                        let goal_param = skill_param.split("/")
                        game_main.data.updateGoals(parseInt(goal_param[0]), parseInt(goal_param[1]))
                        break
                    case BoidSkill.D_Summon_TeamT:
                        let summon_team_line = [this.order_line, this.order_line + 1, this.order_line - 1]
                        for (let t = 0; t < parseInt(summon_team_line.length); t++) {
                            if (summon_team_line[t] < 0 || summon_team_line[t] >= WayInfo.col) {
                                continue
                            }
                            let insertNode = game_main.boidsManager.insertMonster(summon_team_line[t], parseInt(skill_param))
                            let posY = this.node.y
                            posY += 20
                            if (posY > 0) {
                                posY = 0
                            }
                            insertNode.y = posY
                        }
                        break
                    case BoidSkill.D_Summon_TeamD:
                        let summon_team_line_down = [this.order_line, this.order_line + 1, this.order_line - 1]
                        for (let t = 0; t < parseInt(summon_team_line_down.length); t++) {
                            if (summon_team_line_down[t] < 0 || summon_team_line_down[t] >= WayInfo.col) {
                                continue
                            }
                            let insertNode = game_main.boidsManager.addMonsterBottom(summon_team_line_down[t], parseInt(skill_param), true)
                            let posY = this.node.y
                            posY -= 20
                            if (posY > 0) {
                                posY = 0
                            }
                            insertNode.y = posY
                        }
                        break
                    case BoidSkill.D_AroundAcc:
                        let AccPos = this.getWorldPos()
                        let AccParam = this.info.skillParam.split("/")
                        for (let i = 0; i < AccParam.length; i++) {
                            AccParam[i] = parseInt(AccParam[i])
                        }
                        let AccBuff = {
                            uid: BoidSkill.D_AroundAcc,
                            key: BoidBuff.Accelerate,
                            value: AccParam[1],
                            time: AccParam[2]
                        }
                        for (let i = game_main.boidsManager.boids_list.length - 1; i >= 0; i--) {
                            let near_boid = game_main.boidsManager.boids_list[i]
                            if (!near_boid.canAttack()) {
                                continue
                            }
                            if (this.orderId == near_boid.orderId) {
                                continue
                            }
                            let boidsWorldPos = near_boid.getWorldPos()
                            if (AccPos.sub(boidsWorldPos).mag() < AccParam[0] * near_boid.node.scale) {
                                near_boid.addBuff(AccBuff)
                            }
                        }
                        break
                    case BoidSkill.C_Back:
                        if (this.getBuff(BoidBuff.EXLife) <= 0) {
                            game_main.boidsManager.gameFail()
                            return
                        } else {
                            let ExbuffInfo = this.getDelBuffInfo(BoidBuff.EXLife, GetBuffType.KEY)
                            let goMonScript = game_main.boidsManager.addMonster(this.order_line, ExbuffInfo.monsterId)
                            goMonScript.status = BoidStatus.Rolling
                        }

                        let damegeSaveValue = this.getBuff(BoidBuff.DamegeSave)
                        if (damegeSaveValue > 0) {
                            game_main.data.hp += damegeSaveValue
                            game_main.data.updateHp()
                        }
                        break
                    case BoidSkill.C_Goon:
                        if (this.getBuff(BoidBuff.EXLife) <= 0) {
                            game_main.boidsManager.gameWin()
                            return
                        } else {
                            let ExbuffInfo = this.getDelBuffInfo(BoidBuff.EXLife, GetBuffType.KEY)
                            let goMonScript = game_main.boidsManager.addMonster(this.order_line, ExbuffInfo.monsterId)
                            goMonScript.status = BoidStatus.Rolling
                        }
                        break
                }
            }
        }
    },
    // 首次攻击技能
    firstSkill() {
        if (this.info && this.info.skill) {
            let skill_list = this.info.skill.split("#")
            let skill_param_list
            if (this.info.skillParam)
                skill_param_list = this.info.skillParam.split("#")

            for (let i = 0; i < skill_list.length; i++) {
                let skill_param
                if (skill_param_list)
                    skill_param = skill_param_list[i]
                switch (parseInt(skill_list[i])) {
                    case BoidSkill.F_Hide:
                        let HideBuff = {
                            key: BoidBuff.Hide,
                            value: 1,
                            time: parseFloat(skill_param)
                        }
                        this.collision.enabled = false
                        this.node.opacity = 150
                        this.addBuff(HideBuff)
                        break
                    case BoidSkill.F_HideWalk:
                        let hide_walk_param = skill_param.split("/")
                        let HideWalkBuff = {
                            key: BoidBuff.Hide,
                            value: 1,
                            time: parseFloat(hide_walk_param[0])
                        }
                        let HideAccBuff = {
                            key: BoidBuff.Accelerate,
                            value: parseInt(hide_walk_param[1]),
                            time: parseFloat(hide_walk_param[0])
                        }
                        this.collision.enabled = false
                        this.node.opacity = 150
                        this.addBuff(HideWalkBuff)
                        this.addBuff(HideAccBuff)
                        break
                }
            }
        }
    },
    // 攻击技能
    attackSkill() {
        if (this.info && this.info.skill) {
            let skill_list = this.info.skill.split("#")
            let skill_param_list
            if (this.info.skillParam)
                skill_param_list = this.info.skillParam.split("#")
            for (let i = 0; i < skill_list.length; i++) {
                let skill_param
                if (skill_param_list)
                    skill_param = skill_param_list[i]
                switch (parseInt(skill_list[i])) {
                    case BoidSkill.A_Down_Role:
                        let delRole
                        for (let tkey in Tower2Way) {
                            if (Tower2Way[tkey].indexOf(this.order_line) >= 0 && game_main.control.getPlaceStatus(CardType.ROLE, tkey)) {
                                delRole = tkey
                                break
                            }
                        }
                        if (!delRole) {
                            for (let tIndex = 0; tIndex < TowerList.length; tIndex++) {
                                let name = TowerList[tIndex].x + '_' + TowerList[tIndex].y + '_' + TowerList[tIndex].z
                                if (game_main.control.getPlaceStatus(CardType.ROLE, name)) {
                                    delRole = name
                                    break
                                }
                            }
                        }
                        if (delRole) {
                            game_main.control.towerScript[delRole].delTowerRole()
                        } else {
                            game_main.data.beAttacked(1)
                        }
                        // 先判断临近的炮塔
                        // 再判断所有炮塔
                        break
                    case BoidSkill.C_Goon:
                        let backMon = game_main.boidsManager.addMonsterBottom(this.order_line, skill_param)
                        let backMonScript = backMon.getComponent("monster")
                        let saveDamegeBuff = {
                            key: BoidBuff.DamegeSave,
                            value: this.damege,
                        }
                        backMonScript.HP = this.HP
                        backMonScript.addBuff(saveDamegeBuff)
                        let currentExLife = this.getBuffList(BoidBuff.EXLife)
                        for(let exLifeIndex = 0; exLifeIndex < currentExLife.length;exLifeIndex ++){
                            backMonScript.addBuff(currentExLife[i])
                        }
                        break
                }
            }
        }
    },
    // 初始化技能
    initSkill() {
        if (this.info && this.info.skill) {
            let skill_list = this.info.skill.split("#")
            let skill_param_list
            if (this.info.skillParam)
                skill_param_list = this.info.skillParam.split("#")
            for (let i = 0; i < skill_list.length; i++) {
                let skill_param
                if (skill_param_list)
                    skill_param = skill_param_list[i]
                switch (parseInt(skill_list[i])) {
                    case BoidSkill.I_Skill:
                        this.miss = parseInt(skill_param)
                        break
                }
            }
        }
    },
    // 清空时
    clearSkill() {
        if (this.info && this.info.skill) {
            let skill_list = this.info.skill.split("#")
            let skill_param_list
            if (this.info.skillParam)
                skill_param_list = this.info.skillParam.split("#")
            for (let i = 0; i < skill_list.length; i++) {
                let skill_param
                if (skill_param_list)
                    skill_param = skill_param_list[i]
                switch (parseInt(skill_list[i])) {
                    case BoidSkill.C_Back:
                        if (this.HP <= 0) {
                            return
                        }
                        let CO = parseInt(WayInfo.col * Math.random())
                        let goMonScript = game_main.boidsManager.addMonster(CO, skill_param)
                        goMonScript.HP = this.HP
                        goMonScript.status = BoidStatus.Rolling
                        
                        let currentExLife = this.getBuffList(BoidBuff.EXLife)
                        for(let exLifeIndex = 0; exLifeIndex < currentExLife.length;exLifeIndex ++){
                            goMonScript.addBuff(currentExLife[i])
                        }
                        break
                }
            }
        }
    },
    missAni() {
        console.log("Miss动画")
    },
    attack() {
        this._super()
    },
});
